#include "StdAfx.h"
#include "Helpers.h"
#include "FillMaximalGroupAlgorithmUnitTests.h"
#include "FillGroupAlgorithmSinglesUnitTests.h"
#include "Group.h"
#include "Graph.h"
#include "Helpers.h"

extern Vertex* CreateVertex(bool* nameArr, int size);

// tests without input
// create group, insert and remove vertices to it 

// test a graph with n=4,w=2
// iterationNum = number of iterations of FillMaximalGroupAlgorithm to run.
// startCouplesPercent = how many vertices to add to the group before starting couples Fill
// stopCouplesPercent =  how many vertices to add to the group with couples Fill before resorting back to
// singles fill
TestUtils::TestResult FillMaximalGroup4On2(int iterationNum, int startCouplesPercent, int stopCouplesPercent)
{
	// Scenario: creates graph over vertices with  n=4, w=2 
	// creates a group with 1 vertex, tries to improve it should be able to add 1 vertex
	// afterwards, make sure the group has the original vertex.
	
	// Group = 1100
	// Graph = 0110, 0011, 1001, 0101, 1010
	// when looking for couples to add to a group, we don't want the graph to go over 
	// more than 40 couples..
	Graph graph(40);
	Group group(0);
	Vertex* v = CreateGraph4On2AndSetGroup(graph, group);

	// try to improve the group. 
	// try to improve with 3 iterations
	// should be able to add one vertex: 0011
	// there is no size limitation
	GreedyFillMaximalGroupAlgorithm::Fill(graph,group, iterationNum, startCouplesPercent, stopCouplesPercent,30, NULL);
	map<vector<bool>, Vertex*>* vertices = VertexDirectory::GetStaticCopyVertices();
	
	//validate results:
	// make sure the group has the right size and containes the right vertices
	if (TestUtils::VerifyIsTrue(group.Size() == 2,"The group doesn't contain the right number of vertices") == TestUtils::TestFailed)
	{
		return TestUtils::TestFailed;
	}

	if (TestUtils::VerifyIsTrue((group.IsVertexInGroup(v->Name())) == true,"The group doesn't contain the right vertices") == TestUtils::TestFailed)
	{
		return TestUtils::TestFailed;
	}

	bool name[] = {0,0,1,1};
	int n = 4;
	v = CreateVertex(name,n);
	if (TestUtils::VerifyIsTrue((group.IsVertexInGroup(v->Name())) == true,"The group doesn't contain the right vertices") == TestUtils::TestFailed)
	{
		return TestUtils::TestFailed;
	}

	// check that the directory was updated correctly: All vertices in the graph appear in the graph. All vertices
	// in the group point to the right group.
	if (Algorithms::ValidateVertexDirectoryState(&graph, &group) == false)
	{
		return TestUtils::TestFailed;
	}

	return TestUtils::TestPassed;
}

// Try to improve a group using the FIllMaximalGroup algorithm but without initial fiiling of the group
// iterationNum = number of iterations of FillMaximalGroupAlgorithm to run.
// startCouplesPercent = how many vertices to add to the group before starting couples Fill
// stopCouplesPercent =  how many vertices to add to the group with couples Fill before resorting back to
// singles fill
TestUtils::TestResult FillMaximalGroup4On2WithoutInitialFilling(int iterationNum, int startCouplesPercent, int stopCouplesPercent)
{
	// Scenario: creates graph over vertices with  n=4, w=2 
	// creates a group with 1 vertex, tries to improve it. should be able to add 1 vertex
	// or replace the group with a group with 2 vertices
	// afterwards, make sure the group is of size 2 and independent
	
	// Group = 1100
	// Graph = 0110, 0011, 1001, 0101, 1010
	// when looking for couples to add to a group, we don't want the graph to go over 
	// more than 40 couples..
	Graph graph(40);
	Group group(0);
	Vertex* v = CreateGraph4On2AndSetGroup(graph, group);

	// try to improve the group. 
	// there is no size limitation
	// last parameter is false: don't use initial filling
	GreedyFillMaximalGroupAlgorithm::Fill(graph,group,iterationNum,startCouplesPercent,stopCouplesPercent,30, false);
	map<vector<bool>, Vertex*>* vertices = VertexDirectory::GetStaticCopyVertices();
	
	//validate results:
	// make sure the group has the right size and is independent
	if (TestUtils::VerifyIsTrue(group.Size() == 2,"The group doesn't contain the right number of vertices") == TestUtils::TestFailed)
	{
		return TestUtils::TestFailed;
	}

	//check the group is independant
	if (TestUtils::VerifyIsTrue(Algorithms::ValidateGroupIsIndependent(&group) == true,"The group isn't independent") == TestUtils::TestFailed)
	{
		return TestUtils::TestFailed;
	}

	// check that the directory was updated correctly: All vertices in the graph appear in the graph. All vertices
	// in the group point to the right group.
	if (Algorithms::ValidateVertexDirectoryState(&graph, &group) == false)
	{
		return TestUtils::TestFailed;
	}

	return TestUtils::TestPassed;
}

// Try to improve a group using the FIllMaximalGroup algorithm but without initial fiiling of the group
// iterationNum = number of iterations of FillMaximalGroupAlgorithm to run.
// stopCouplesPercent =  how many vertices to add to the group with couples Fill before resorting back to
// singles fill
TestUtils::TestResult FillMaximalGroup4On2WithoutInitialFillingWithoutCuplesFill(int iterationNum, int stopCouplesPercent)
{
	// Scenario: creates graph over vertices with  n=4, w=2 
	// creates a group with 1 vertex, tries to improve it. should be able to add 1 vertex,
	// or replace the group with a group with 2 vertices. in this run the couples fill isn't used
	
	// Group = 1100
	// Graph = 0110, 0011, 1001, 0101, 1010
	// when looking for couples to add to a group, we don't want the graph to go over 
	// more than 40 couples..
	Graph graph(40);
	Group group(0);
	Vertex* v = CreateGraph4On2AndSetGroup(graph, group);

	// try to improve the group. 
	// we start running couples fill when the group has reached its original size. 
	// this means we won't improve the group with couples fill
	// should be able to reach a group of size 2
	// there is no size limitation
	// last parameter is false: don't use initial filling
	GreedyFillMaximalGroupAlgorithm::Fill(graph,group,iterationNum,100,stopCouplesPercent,30, false);
	map<vector<bool>, Vertex*>* vertices = VertexDirectory::GetStaticCopyVertices();
	
	//validate results:
	// make sure the group has the right size and is independent
	if (TestUtils::VerifyIsTrue(group.Size() == 2,"The group doesn't contain the right number of vertices") == TestUtils::TestFailed)
	{
		return TestUtils::TestFailed;
	}

	//check the group is independant
	if (TestUtils::VerifyIsTrue(Algorithms::ValidateGroupIsIndependent(&group) == true,"The group isn't independent") == TestUtils::TestFailed)
	{
		return TestUtils::TestFailed;
	}

	// check that the directory was updated correctly: All vertices in the graph appear in the graph. All vertices
	// in the group point to the right group.
	if (Algorithms::ValidateVertexDirectoryState(&graph, &group) == false)
	{
		return TestUtils::TestFailed;
	}

	return TestUtils::TestPassed;
}

TestUtils::TestResult FillMaximalEmptyGroup4On2()
{
	// Scenario: creates graph over vertices with  n=4, w=2 
	// Try to fill an empty group - should be able to add 2 vertices
	
	// Graph = 0110, 0011, 1001, 0101, 1010, 1100
	// when looking for couples to add to a group, we don't want the graph to go over 
	// more than 40 couples..
	Graph graph(40);
	Group group(0);
	graph = TestUtils::CreateGraph4On2(graph);

	// try to improve the group
	// should be able to add 2 vertices
	// there is no size limitation
	GreedyFillMaximalGroupAlgorithm::Fill(graph,group,1,0,50,30, NULL);
	map<vector<bool>, Vertex*>* vertices = VertexDirectory::GetStaticCopyVertices();
	
	//validate results:
	// make sure the group has the right size and is independent
	if (TestUtils::VerifyIsTrue(group.Size() == 2,"The group doesn't contain the right number of vertices") == TestUtils::TestFailed)
	{
		return TestUtils::TestFailed;
	}

	//check the group is independant
	if (TestUtils::VerifyIsTrue(Algorithms::ValidateGroupIsIndependent(&group) == true,"The group isn't independent") == TestUtils::TestFailed)
	{
		return TestUtils::TestFailed;
	}	

	// check that the directory was updated correctly: All vertices in the graph appear in the graph. All vertices
	// in the group point to the right group.
	if (Algorithms::ValidateVertexDirectoryState(&graph, &group) == false)
	{
		return TestUtils::TestFailed;
	}

	return TestUtils::TestPassed;
}



